<!doctype html>
<html lang="en">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta name="description" content="coinfaces">

        <title>简单设置Pelican</title>

    <link rel="stylesheet" href="../../theme/css/style.css">
    <link rel="stylesheet" href="../../theme/css/pygments.css">



</head>

<body>
    <div class="content">
<h1>简单设置Pelican</h1>    <p>
        under
            <a href="../../tags/pelican/">pelican</a>
            <a href="../../tags/blog/">blog</a>
    </p>
    <p>
        in <a href="../../categories/tech/">tech</a>
    </p>
    <p>Published: 2016-04-05</p>


    <p><a class="reference external" href="http://docs.getpelican.com/">Pelican</a>是用<a class="reference external" href="https://www.python.org/">Python</a>实现的静态站点生成软件，它可以将<a class="reference external" href="http://docutils.sourceforge.net/rst.html">reStructedText</a>或<a class="reference external" href="https://daringfireball.net/projects/markdown/">Markdown</a>格式的文件转化为HTML，通过预设定的模板，生成一个完整的网站，将用户从HTML编辑和重复的工作中解脱出来。</p>
<p>这篇文章的内容基于Pelican 3.6.3.</p>
<div class="section" id="id2">
<h2>运行Pelican</h2>
<p>首先要安装Pelican，流行Linux发行版一般都打包了Pelican，用包管理器直接安装即可。由于各种原因，用户可能需要自己在Python环境里安装Pelican，这方面的信息可以参照<a class="reference external" href="http://docs.getpelican.com/en/3.6.3/install.html">Pelican的文档</a>，安装完后，应该能在shell里直接运行<tt class="docutils literal">pelican</tt>命令。</p>
<p>运行Pelican前，先为站点有关的文件单独建立一个目录，并<tt class="docutils literal">cd</tt>进去。用<tt class="docutils literal"><span class="pre">pelican-quickstart</span></tt>能快速地在这个目录里部署Pelican的开发辅助脚本，新手可能会搞不懂这些文件的用途，为了使这个过程更加易懂，这里只使用<tt class="docutils literal">pelican</tt>命令和一个简单的配置文件。</p>
<p>如果直接输入<tt class="docutils literal">pelican</tt>命令，尽管会输出一些警告信息，Pelican还是会生成一个完整的站点，运行<tt class="docutils literal">(cd output &amp;&amp; python <span class="pre">-m</span> pelican.server)</tt>命令的话，就能在<a class="reference external" href="http://127.0.0.1:8000/">http://127.0.0.1:8000/</a>看到这个站点，它的界面是Pelican的默认设置。输入<tt class="docutils literal">Ctrl+C</tt>可停止该网页服务。</p>
<p>默认情况下，Pelican会试图在当前工作目录寻找输入文件，这会将输入文件和输出文件以及可能的配置文件混在一起，所以一般会为输入文件建立一个单独的目录，一般都用“content”作为目录名，此后需要输入<tt class="docutils literal">pelican content</tt>使Pelican在该目录下寻找输入文件。</p>
</div>
<div class="section" id="id4">
<h2>配置Pelican</h2>
<p>配置文件可以起到很多作用：减少输入和重复的工作，使用户更好地控制Pelican的运行等。这里使用默认的Pelican配置文件名“pelicanconf.py”，使用“-s &lt;config_path&gt;”可以指定其它配置文件。这个配置文件实际上是一个Python模块文件，注释以“#”开头，变量名区分大小写。Pelican规定设置名只能包含大写字母和下划线。在<a class="reference external" href="http://docs.getpelican.com/en/3.6.3/settings.html">Pelican的文档</a>可以找到Pelican用到的设置名及其默认值。</p>
<p>Pelican配置文件一般用以下两行开头：</p>
<pre class="literal-block">
# -*- coding: utf-8 -*-
from __future__ import unicode_literals
</pre>
<p>这不是强制的，但对于包含了非ASCII字符的文件来说非常重要，第一行注释规定了文件的编码，如果不是以“utf-8”编码，应该改成实际的文本编码，否则Pelican将无法运行，第二行自动将所有的字符串常量转化成了unicode类型，这样字符串表示的文本就没有歧义。在Python里，字符串可以包含在单引号<tt class="docutils literal">''</tt>或双引号<tt class="docutils literal">&quot;&quot;</tt>里。</p>
<div class="section" id="id6">
<h3>网站信息</h3>
<p><tt class="docutils literal">SITENAME</tt>定义网站名，很多主题会把它放在主页上，<tt class="docutils literal">AUTHOR</tt>定义了网站的默认作者，如果网站里使用了不止一种语言，<tt class="docutils literal">DEFAULT_LANG</tt>能决定默认显示的语言。</p>
</div>
<div class="section" id="id7">
<h3>输入文件</h3>
<p>在配置文件中可以用<tt class="docutils literal">PATH</tt>设置输入文件的默认位置，这样便可以省略<tt class="docutils literal">pelican</tt>命令后面的内容目录。在Pelican里大概有三种类型的内容，静态文件、页面和文章。静态文件被直接复制到目标站点中，例如图标，.htaccess文件，这里将这些文件放在内容目录的（下同）子目录“static”中。页面是没有日期属性的内容，例如网站的自我介绍页面，这些内容存放在“pages”子目录中。文章是和特定日期关联的内容，在Pelican里，所有的文章还需要有类别属性，这里指定同一类别的所有文章单独占一个子目录，子目录的名称即为类别名，如下所示：</p>
<pre class="literal-block">
PATH = 'content'
PAGE_PATHS = ['pages']
STATIC_PATHS = ['static']
USE_FOLDER_AS_CATEGORY = True
</pre>
<p>在Python里，方括号用来表示列表，里面可以包含多个值（在后面会看到例子），<tt class="docutils literal">True</tt>和<tt class="docutils literal">False</tt>就表示逻辑的真和假。</p>
<p>除了类别，在输入文件的路径里还包含其它信息，这些信息可以被用于设置文章的属性，<tt class="docutils literal">FILENAME_METADATA</tt>就起到了这个作用，它是一个正则表达式，如果它匹配了一篇文章的文件名（不含文件后缀），其各组匹配的内容就被设置为和组同名的文章属性。但这个正则表达式无法匹配页面名，因为页面没有日期属性，这时可以用<tt class="docutils literal">SLUGIFY_SOURCE</tt>来设置页面的slug（用在URL里的标题）。以下设置会从文章的文件名中设置其日期、slug和语言属性，并用文件名（不含后缀）作为页面的slug。</p>
<pre class="literal-block">
FILENAME_METADATA = '(?P&lt;date&gt;\d{8})-?(?P&lt;slug&gt;\w*)-?(?P&lt;lang&gt;\w*)'
SLUGIFY_SOURCE = 'basename'
</pre>
</div>
<div class="section" id="id8">
<h3>输出设置</h3>
<p>Pelican默认使用以“.html”结尾的URL，可以设置Pelican使用以“/”结尾的URL，只要将<tt class="docutils literal">ARTICLE_SAVE_AS</tt>和<tt class="docutils literal">PAGE_SAVE_AS</tt>分别设置为<tt class="docutils literal">ARTICLE_URL</tt>和<tt class="docutils literal">PAGE_URL</tt>加“index.html”即可：</p>
<pre class="literal-block">
ARTICLE_URL = 'posts/{category}/{date:%Y%m}/{slug}/'
ARTICLE_SAVE_AS = ARTICLE_URL + 'index.html'
PAGE_URL = 'pages/{slug}/'
PAGE_SAVE_AS = PAGE_URL + 'index.html'
</pre>
<p>在上面的设置中，文章在“posts”子目录下，并按照类别和日期存放，最后一级URL为它的slug，页面无类别和日期属性，在“pages”目录下按slug分别存放即可。</p>
<p>目标站点里的所有文章可以通过一个索引页面访问被访问到，在Pelican里这个页面叫做“index”，随着时间增长，这个页面里的内容会越来越多，增加其加载时间且影响可读性。把这个大页面分解成多个小页面（pagination）可以解决这个问题，例如<tt class="docutils literal">DEFAULT_PAGINATION = 10</tt>将每个小页面可包含的文章索引数限制为最多10个。</p>
<p>文章还可以按作者、类别和关键字浏览。例如为了支持按作者浏览，Pelican会在一个页面上列出所有的作者，并为每个作者再建立一个页面，里面列出了这个作者的所有文章，用<tt class="docutils literal">AUTHORS_SAVE_AS</tt>、<tt class="docutils literal">AUTHOR_URL</tt>和<tt class="docutils literal">AUTHOR_SAVE_AS</tt>可以控制这些页面的URL：</p>
<pre class="literal-block">
AUTHOR_URL = 'authors/{slug}/'
AUTHOR_SAVE_AS = AUTHOR_URL + 'index.html'
AUTHORS_SAVE_AS = 'authors/index.html'
</pre>
<p>Pelican没有&quot;AUTHORS_URL&quot;这个选项。</p>
<p>Pelican还支持按时间归档文章，这些归档称为archives，可以按年、月或日进行归档。如果不需要归档，可以覆盖<tt class="docutils literal">DIRECT_TEMPLATES</tt>设置，在新的设置里不包含“archives”即可：</p>
<pre class="literal-block">
DIRECT_TEMPLATES = ['index', 'categories', 'tags', 'authors']
</pre>
<p>这可以避免Pelican生成“archives”页面</p>
<p>设置<tt class="docutils literal">RELATIVE_URLS = True</tt>可以让站点用相对路径作为站内链接，这样就有可能将生成的站点挂在一个子目录下，有的主题会假定站点用绝对路径作为站内链接，这些主题将不能正常工作。</p>
<p>Feeds可以将站点更新通知用户，<tt class="docutils literal">SITEURL</tt>要设置好，否则生成的feeds是没用的，<tt class="docutils literal">TIMEZONE</tt>最好也设置为读者所在的时区。如果不想生成feeds，可以将有关设置都改为<tt class="docutils literal">None</tt>。</p>
<p>有的静态文件在托管环境（例如GitHub Pages）中有特殊意义，这些文件一般要放置在目标站点的根目录下，但默认情况下静态文件被放置在站点的“static”子目录里。这里可以设置<tt class="docutils literal">PATH_METADATA</tt>将静态文件放在站点根目录下，也可以在<tt class="docutils literal">EXTRA_PATH_METADATA</tt>里为这些文件单独指定路径，用<tt class="docutils literal">EXTRA_PATH_METADATA</tt>的将“.nojekyll”和“CNAME”放在目标站点根目录中的解决方案如下：</p>
<pre class="literal-block">
EXTRA_PATH_METADATA = {
  'static/.nojekyll': {'path': '.nojekyll'},
  'static/CNAME': {'path': 'CNAME'},
}
</pre>
</div>
<div class="section" id="id9">
<h3>主题</h3>
<p>Pelican 3.6.3自带了两个主题“notmyidea”（默认主题）和“simple”，可为<tt class="docutils literal">THEME</tt>选择任何一个设置。“notmyidea”还定义了自己的设置项，如果要使用这些设置项，最好将其列在<tt class="docutils literal">THEME</tt>后面。</p>
<p>综上所述，完整的“pelicanconf.py”：</p>
<div class="highlight"><pre><span></span><span class="c1"># -*- coding: utf-8 -*-</span>

<span class="kn">from</span> <span class="nn">__future__</span> <span class="kn">import</span> <span class="n">unicode_literals</span>


<span class="c1"># 站点信息</span>
<span class="n">AUTHOR</span> <span class="o">=</span> <span class="s1">&#39;jpli&#39;</span>
<span class="n">SITENAME</span> <span class="o">=</span> <span class="s1">&#39;coinfaces&#39;</span>
<span class="n">DEFAULT_LANG</span> <span class="o">=</span> <span class="s1">&#39;en&#39;</span>


<span class="c1"># 输入目录：content</span>
<span class="c1"># 静态内容：content/static</span>
<span class="c1"># 页面：content/pages/&lt;slug&gt;.rst</span>
<span class="c1"># 文章：content/&lt;日期&gt;-&lt;slug&gt;-&lt;语言&gt;.rst</span>
<span class="n">PATH</span> <span class="o">=</span> <span class="s1">&#39;content&#39;</span>
<span class="n">PAGE_PATHS</span> <span class="o">=</span> <span class="p">[</span><span class="s1">&#39;pages&#39;</span><span class="p">]</span>
<span class="n">STATIC_PATHS</span> <span class="o">=</span> <span class="p">[</span><span class="s1">&#39;static&#39;</span><span class="p">]</span>
<span class="n">USE_FOLDER_AS_CATEGORY</span> <span class="o">=</span> <span class="kc">True</span>
<span class="n">FILENAME_METADATA</span> <span class="o">=</span> <span class="s1">&#39;(?P&lt;date&gt;\d</span><span class="si">{8}</span><span class="s1">)-?(?P&lt;slug&gt;\w*)-?(?P&lt;lang&gt;\w*)&#39;</span>
<span class="n">SLUGIFY_SOURCE</span> <span class="o">=</span> <span class="s1">&#39;basename&#39;</span>


<span class="c1"># URL</span>
<span class="c1">#</span>
<span class="c1"># 文章：posts/&lt;类别&gt;/&lt;年&gt;&lt;月&gt;/&lt;slug&gt;/</span>
<span class="c1"># 文章翻译：posts/&lt;类别&gt;/&lt;年&gt;&lt;月&gt;/&lt;slug&gt;-&lt;语言&gt;/</span>
<span class="c1"># 页面：pages/&lt;slug&gt;/</span>
<span class="c1">#</span>
<span class="c1"># 所有类别：categories/</span>
<span class="c1"># 类别：categories/&lt;slug&gt;/</span>
<span class="c1"># 所有关键字：tags/</span>
<span class="c1"># 关键字：tags/&lt;slug&gt;/</span>
<span class="c1"># 所有作者：authors/</span>
<span class="c1"># 作者：authors/&lt;slug&gt;/</span>

<span class="n">ARTICLE_URL</span> <span class="o">=</span> <span class="s1">&#39;posts/</span><span class="si">{category}</span><span class="s1">/{date:%Y%m}/</span><span class="si">{slug}</span><span class="s1">/&#39;</span>
<span class="n">ARTICLE_SAVE_AS</span> <span class="o">=</span> <span class="n">ARTICLE_URL</span> <span class="o">+</span> <span class="s1">&#39;index.html&#39;</span>

<span class="n">ARTICLE_LANG_URL</span> <span class="o">=</span> <span class="s1">&#39;posts/</span><span class="si">{category}</span><span class="s1">/{date:%Y%m}/</span><span class="si">{slug}</span><span class="s1">-</span><span class="si">{lang}</span><span class="s1">/&#39;</span>
<span class="n">ARTICLE_LANG_SAVE_AS</span> <span class="o">=</span> <span class="n">ARTICLE_LANG_URL</span> <span class="o">+</span> <span class="s1">&#39;index.html&#39;</span>

<span class="n">PAGE_URL</span> <span class="o">=</span> <span class="s1">&#39;pages/</span><span class="si">{slug}</span><span class="s1">/&#39;</span>
<span class="n">PAGE_SAVE_AS</span> <span class="o">=</span> <span class="n">PAGE_URL</span> <span class="o">+</span> <span class="s1">&#39;index.html&#39;</span>

<span class="c1"># 不使用归档</span>
<span class="n">DIRECT_TEMPLATES</span> <span class="o">=</span> <span class="p">[</span><span class="s1">&#39;index&#39;</span><span class="p">,</span> <span class="s1">&#39;categories&#39;</span><span class="p">,</span> <span class="s1">&#39;tags&#39;</span><span class="p">,</span> <span class="s1">&#39;authors&#39;</span><span class="p">]</span>

<span class="n">CATEGORY_URL</span> <span class="o">=</span> <span class="s1">&#39;categories/</span><span class="si">{slug}</span><span class="s1">/&#39;</span>
<span class="n">CATEGORY_SAVE_AS</span> <span class="o">=</span> <span class="n">CATEGORY_URL</span> <span class="o">+</span> <span class="s1">&#39;index.html&#39;</span>
<span class="n">CATEGORIES_SAVE_AS</span> <span class="o">=</span> <span class="s1">&#39;categories/index.html&#39;</span>

<span class="n">TAG_URL</span> <span class="o">=</span> <span class="s1">&#39;tags/</span><span class="si">{slug}</span><span class="s1">/&#39;</span>
<span class="n">TAG_SAVE_AS</span> <span class="o">=</span> <span class="n">TAG_URL</span> <span class="o">+</span> <span class="s1">&#39;index.html&#39;</span>
<span class="n">TAGS_SAVE_AS</span> <span class="o">=</span> <span class="s1">&#39;tags/index.html&#39;</span>

<span class="n">AUTHOR_URL</span> <span class="o">=</span> <span class="s1">&#39;authors/</span><span class="si">{slug}</span><span class="s1">/&#39;</span>
<span class="n">AUTHOR_SAVE_AS</span> <span class="o">=</span> <span class="n">AUTHOR_URL</span> <span class="o">+</span> <span class="s1">&#39;index.html&#39;</span>
<span class="n">AUTHORS_SAVE_AS</span> <span class="o">=</span> <span class="s1">&#39;authors/index.html&#39;</span>

<span class="n">EXTRA_PATH_METADATA</span> <span class="o">=</span> <span class="p">{</span>
    <span class="s1">&#39;static/.nojekyll&#39;</span><span class="p">:</span> <span class="p">{</span><span class="s1">&#39;path&#39;</span><span class="p">:</span> <span class="s1">&#39;.nojekyll&#39;</span><span class="p">},</span>
    <span class="s1">&#39;static/CNAME&#39;</span><span class="p">:</span> <span class="p">{</span><span class="s1">&#39;path&#39;</span><span class="p">:</span> <span class="s1">&#39;CNAME&#39;</span><span class="p">},</span>
<span class="p">}</span>


<span class="c1"># 分页，每个页面最多列出10条索引</span>
<span class="n">DEFAULT_PAGINATION</span> <span class="o">=</span> <span class="mi">10</span>

<span class="c1"># 站内URL使用相对路径</span>
<span class="n">RELATIVE_URLS</span> <span class="o">=</span> <span class="kc">True</span>


<span class="c1"># 不生成feed</span>
<span class="n">FEED_ALL_ATOM</span> <span class="o">=</span> <span class="kc">None</span>
<span class="n">CATEGORY_FEED_ATOM</span> <span class="o">=</span> <span class="kc">None</span>
<span class="n">TRANSLATION_FEED_ATOM</span> <span class="o">=</span> <span class="kc">None</span>
<span class="n">AUTHOR_FEED_ATOM</span> <span class="o">=</span> <span class="kc">None</span>
<span class="n">AUTHOR_FEED_RSS</span> <span class="o">=</span> <span class="kc">None</span>

<span class="n">TIMEZONE</span> <span class="o">=</span> <span class="s1">&#39;UTC&#39;</span>


<span class="c1"># 主题</span>
<span class="n">THEME</span> <span class="o">=</span> <span class="s1">&#39;simple&#39;</span>
</pre></div>
<p>（完）</p>
</div>
</div>

    </div>
<nav class="nav sidebar">
    <div class="siteinfo">
        <div class="sitename"><a href="../..">coinfaces</a></div>
        <div class="tagline">Another Side of Life</div>
    </div>

        <a href="../../categories/">categories</a>
        <a href="../..">&larr; Home</a>
</nav><footer class="footer">
    <span>
        &copy; jpli &middot;
        under <a rel="license" href="http://creativecommons.org/licenses/by-sa/4.0/">CC-BY-SA 4.0</a>
    </span>
    |
    <span>
        Powered by:
        <a href="http://blog.getpelican.com/">Pelican</a>
    </span>
</footer></body>
</html>